﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Web.Script.Serialization;
using System.Xml.Linq;
//
namespace PerceptiveMCAPI.Types
{
   public class campaignClickStatsOutput : Api_BaseOutput
   {
      public List<campaignClickStatsResults> result { get; set; }
      public campaignClickStatsParms inputParms { get; private set; }
      // --------------------------------------------------------
      public campaignClickStatsOutput( campaignClickStatsInput input )
         : base( input )
      {
         inputParms = input.parms;
         result = new List<campaignClickStatsResults>();
      }
      // --------------------------------------------------- tostring
      public override string ToString()
      {
         return string.Format( "cid: {0}, clickStats entry count: {1}",
            inputParms.cid, result.Count );
      }

      #region ================================================================== format setup

      // ---- serial
      internal void Format( string api_Request, string api_Response )
      {
         this.api_Request = api_Request;
         this.api_Response = api_Response;
         // ----------------------------------
         if ( this.api_OutputType == EnumValues.OutputType.JSON )
            outputJSON();
         else if ( this.api_OutputType == EnumValues.OutputType.XML )
            outputXML();
      }

      // ---- xmlrpc
      internal void Format( object rpcResult )
      {
         this.api_Request = EnumValues.NotSupplied;
         this.api_Response = EnumValues.NotSupplied;
         // ------------------------
         this.result = FormatResults( rpcResult );
      }

      #endregion

      #region ================================================================= Output

      // ---------------------------------------------------------- outputXML
      private void outputXML()
      {
         XElement xml = XElement.Parse( this.api_Response );
         // error check
         Api_Error error = apiSerial.GetXmlOutputError( xml );
         if ( error != null )
         {
            this.api_ErrorMessages.Add( error );
            return;
         }
         // -------------------------------------------- get values
         try
         {
            int i;
            IEnumerable<XElement> nodes = xml.Elements( "struct" );
            foreach ( XElement entry in nodes )
            {
               campaignClickStatsResults stats = new campaignClickStatsResults();
               stats.url = entry.Attribute( "key" ).Value;
               int.TryParse( entry.Element( "clicks" ).Value, out i ); stats.clicks = i;
               int.TryParse( entry.Element( "unique" ).Value, out i ); stats.unique = i;
               this.result.Add( stats );
            }
         }
         catch ( Exception ex )
         {
            this.api_ErrorMessages.Add( apiException.FormatError( ex ) );
         }
      }

      // ---------------------------------------------------------- outputJSON
      private void outputJSON()
      {
         JavaScriptSerializer jss = new JavaScriptSerializer();

         try
         {
            if ( this.api_Response.Contains( EnumValues.JSONErrorString ) )
            {
               Api_Error err = jss.Deserialize<Api_Error>( this.api_Response );
               this.api_ErrorMessages.Add( err );
            }
            else
            {
               object jsonResult = jss.Deserialize<object>( this.api_Response );
               this.result = FormatResults( jsonResult );
            }
         }
         catch ( Exception ex )
         {
            this.api_ErrorMessages.Add( apiException.FormatError( ex ) );
         }
      }

      // ---------------------------------------------------------- Formatting
      private List<campaignClickStatsResults> FormatResults( object x_results )
      {
         // ************* NOTE *************************************
         // empty ARRAY is returned, if no click stats -- otherwise 
         // XmlRpcStruct/Dictionary is returned
         // ********************************************************

         int iTemp;
         List<campaignClickStatsResults> results = new List<campaignClickStatsResults>();
         if ( x_results == null || x_results.GetType().IsArray ) return results;
         // ------------------------------------------------------------
         IDictionary idict = x_results as IDictionary;
         foreach ( DictionaryEntry item in idict )
         {
            campaignClickStatsResults stats = new campaignClickStatsResults();
            stats.url = item.Key.ToString();

            IDictionary counts = item.Value as IDictionary;
            int.TryParse( counts["clicks"].ToString(), out iTemp ); stats.clicks = iTemp;
            int.TryParse( counts["unique"].ToString(), out iTemp ); stats.unique = iTemp;

            results.Add( stats );
         }
         // --------------
         return results;
      }

      #endregion
   }
}
